package com.zxl.gtion.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.alibaba.fastjson2.JSON;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.zxl.gtion.dao.SubjectDao;
import com.zxl.gtion.entity.*;
import com.zxl.gtion.service.*;
import com.zxl.gtion.util.ShiroUtils;
import com.zxl.gtion.vo.SimAnswerVO;
import com.zxl.gtion.vo.SubjectVO;
import lombok.RequiredArgsConstructor;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.stream.Collectors;

/**
 * (Subject)表服务实现类
 *
 * @author
 * @since 2024-03-06 16:45:01
 */
@Service("subjectService")
@RequiredArgsConstructor
public class SubjectServiceImpl extends ServiceImpl<SubjectDao, Subject> implements SubjectService {

    private final AnswerService answerService;
    private final AnswerRecordService answerRecordService;
    private final PrizeService prizeService;
    private final UserPrizeService userPrizeService;

    @Override
    public List<SubjectVO> answerInterface() {
        List<Subject> subjects = this.list();
        if (subjects.isEmpty()) {
            return new ArrayList<>();
        }
        List<SubjectVO> subjectVOS = subjects
                .stream().map(e -> BeanUtil.copyProperties(e, SubjectVO.class)).collect(Collectors.toList());
        List<Integer> subjectIDs = subjectVOS.stream().map(SubjectVO::getId).collect(Collectors.toList());
        // 获取这个题目下得所有答案信息
        List<Answer> answers = answerService.lambdaQuery().in(Answer::getSubjectId, subjectIDs).list();
        if (answers.isEmpty()) {
            return subjectVOS;
        }
        // 将所有题目下的答案信息放到题目对象下
        Map<Integer, List<Answer>> subIdAndAnswer = answers.stream().collect(Collectors.groupingBy(Answer::getSubjectId));
        for (SubjectVO subjectVO : subjectVOS) {
            Integer subjectId = subjectVO.getId();
            List<Answer> answers1 = subIdAndAnswer.get(subjectId);
            if (answers1 != null && !answers1.isEmpty()) {
                subjectVO.setAnswers(answers1.stream()
                        .map(e -> BeanUtil.copyProperties(e, SimAnswerVO.class)).collect(Collectors.toList()));
            }
        }
        if (subjectVOS.size() <= 5) {
            return subjectVOS;
        }
        // 从题目中随机抽取5个题目出来
        List<SubjectVO> subjectVOList = new ArrayList<>();
        for (int i = 0; i < 5; i++) {
            Random random = new Random();
            int i1 = random.nextInt(subjectVOS.size());
            SubjectVO subjectVO = subjectVOS.get(i1);
            subjectVOList.add(subjectVO);
            subjectVOS.remove(i1);
        }
        return subjectVOList;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Prize userAnswer(List<SubjectVO> subjectVOS) {
        // 答对多少题
        int i = 0;
        for (SubjectVO subjectVO : subjectVOS) {
            Integer userAnswerId = subjectVO.getUserAnswerId();
            List<Answer> answers = subjectVO.getAnswers().stream()
                    .map(e -> BeanUtil.copyProperties(e, Answer.class)).collect(Collectors.toList());
            for (Answer answer : answers) {
                // 判断选择的答案是否正确
                if (userAnswerId.equals(answer.getId())) {
                    answer.setIsUserAnswer(Answer.IS_USER_ANSWER);
                    String type = answer.getType();
                    if (type.equals("1")) {
                        i++;
                        subjectVO.setIsTrue(Boolean.TRUE);
                    } else {
                        subjectVO.setIsTrue(Boolean.FALSE);
                    }
                }
            }
        }
        // 保存一个用户答题记录
        AnswerRecord answerRecord = new AnswerRecord();
//        answerRecord.setUserId(ShiroUtils.getUserId());
        answerRecord.setUserId(1);
        answerRecord.setAnswerInfo(JSON.toJSONString(subjectVOS));
        answerRecord.setCorrectCount(i);
        answerRecordService.save(answerRecord);

        // 用集合是防止后续如果奖励更新成多个 会报错  就默认领取集合最新的那个
        List<Prize> list = prizeService.lambdaQuery().eq(Prize::getGreat, i).orderByDesc(Prize::getCreateTime).list();
        if (list.isEmpty()) {
            return prizeService.lambdaQuery().eq(Prize::getGreat, 0).list().get(0);
        }
        // 根据用户答对的题 获取prize表里对应的奖励 然后再保存到user_prize表 用户奖励表里。
        Prize prize = list.get(0);
        // 保存用户领取的奖励信息
        UserPrize userPrize = new UserPrize();
        userPrize.setPrizeId(prize.getId());
//        userPrize.setUserId(ShiroUtils.getUserId());
        userPrize.setUserId(1);
        if (StringUtils.isNotEmpty(prize.getImgUrl())) {
            userPrize.setPrizeUrl(prize.getImgUrl());
        }
        if (StringUtils.isNotEmpty(prize.getName())) {
            userPrize.setPrizeName(prize.getName());
        }
        userPrizeService.save(userPrize);
        return prize;
    }

    @Override
    public List<Prize> myPrize() {
        // 根据登录用户的id获取这个用户领取过的所有奖励
        List<UserPrize> collect = userPrizeService.lambdaQuery()
//                .eq(UserPrize::getUserId, ShiroUtils.getUserId())
                .eq(UserPrize::getUserId, "1")
                .orderByDesc(UserPrize::getCreateTime)
                .list();
        if (collect.isEmpty()) {
            return new ArrayList<>();
        }
        List<Prize> prizes = new ArrayList<>();
        Prize prize;
        for (UserPrize userPrize : collect) {
            prize = new Prize();
            prize.setId(userPrize.getPrizeId());
            if (StringUtils.isNotEmpty(userPrize.getPrizeUrl())) {
                prize.setImgUrl(userPrize.getPrizeUrl());
            }
            if (StringUtils.isNotEmpty(userPrize.getPrizeName())) {
                prize.setName(userPrize.getPrizeName());
            }
            prizes.add(prize);
        }
        return prizes;
    }

    @Override
    public Boolean isHavePrize() {
        User userInfo = ShiroUtils.getUserInfo();
        int userId = 0;
        if (userInfo == null) {
            return false;
        }
        long collect = userPrizeService.lambdaQuery()
//                .eq(UserPrize::getUserId, ShiroUtils.getUserId())
                .eq(UserPrize::getUserId, userId)
                .count();
        return collect != 0;
    }


}

